package com.ayg.test.apitest.utils;

import com.ayg.test.apitest.entity.Request;
import com.ayg.test.apitest.entity.TestCase;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import de.sstoehr.harreader.HarReader;
import de.sstoehr.harreader.model.*;
import java.io.File;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class HarUtil {
    public static void main(String[] args)throws Exception{
        String harFilePath = null;
        String ymlFileName = null;
        String[] includeChars = null;
        String[] excludeChars = null;
        System.out.println("=======================har2case 工具=======================");
        switch (args.length){
            case 0:
                printArgsTips();
                return;
            case 1:
                printArgsTips();
                return;
            case 2:
                    harFilePath = args[0];
                    ymlFileName = args[1];
                    break;
            case 3:
                harFilePath = args[0];
                ymlFileName = args[1];
                includeChars = args[2].split("/");
                break;
            case 4:
                harFilePath = args[0];
                ymlFileName = args[1];
                includeChars = args[2].split("/");
                excludeChars = args[3].split("/");
                break;
            default:
                break;
        }


        Gson gson = GsonUtil.buildGson();
        HarReader harReader = new HarReader();
        System.out.println("开始读取har文件并进行解析："+harFilePath);
       // Har har = harReader.readFromFile(new File(HarUtil.class.getResource("/har/chrome-admin-query2.har").getPath()));
        Har har = harReader.readFromFile(new File(harFilePath));
        List<HarEntry> harEntryList = har.getLog().getEntries();
        List<Map> testCases = new ArrayList<>();
        for(HarEntry harEntry: harEntryList){
            HarRequest harRequest = harEntry.getRequest();
           /* if(harRequest.getUrl().contains("api") && !harRequest.getUrl().contains("img-scan")
                    && !harRequest.getUrl().contains("img-scan/erify-codes")) {*/
            String url = harRequest.getUrl();
            if(url == null){
                continue;
            }
            if(containstr(url,includeChars) && !containstr(url,excludeChars)){
                Map testMap = new HashMap();
                TestCase testCase = new TestCase();
                Request request = new Request();
                request.setUrl(harRequest.getUrl());
                request.setMethod(harRequest.getMethod().name());
               // request.setHeaders(harRequest.getHeaders());
                Map paramJson = new HashMap();
                request.setJson(paramJson);
                List<HarQueryParam> harQueryParams = harRequest.getQueryString();
                for(HarQueryParam harQueryParam : harQueryParams){
                    paramJson.put(harQueryParam.getName(),harQueryParam.getValue());
                }
                List<HarPostDataParam> harPostDataParams = harRequest.getPostData().getParams();
                for(HarPostDataParam harPostDataParam : harPostDataParams){
                    paramJson.put(harPostDataParam.getName(),harPostDataParam.getValue());
                }
                String postDataText = harRequest.getPostData().getText();
               // Map postDataTextMap = gson.fromJson(postDataText,Map.class);
                Map postDataTextMap = gson.fromJson(postDataText,new TypeToken<Map<String, Object>>() {}.getType());
                if(postDataTextMap != null) {
                    paramJson.putAll(postDataTextMap);
                }
                List validateList = new ArrayList();
                testCase.setName(request.getUrl().substring(request.getUrl().indexOf("/api")));
                testCase.setType(1);
                testCase.setRequest(request);
                testCase.setValidate(validateList);
                HarResponse harResponse = harEntry.getResponse();
                HarContent harContent = harResponse.getContent();
                Map<String,Object> harContentMap = gson.fromJson(harContent.getText(),Map.class);
                System.out.println(harRequest.getUrl());
                for (Map.Entry<String, Object> entry : harContentMap.entrySet()) {
                    System.out.println("key= " + entry.getKey() + " and value= " + entry.getValue());
                    Map validateMap = new HashMap();
                    if(entry.getValue() instanceof String){
                        validateMap.put("check",entry.getKey());
                        validateMap.put("comparator","eq");
                        validateMap.put("expect",entry.getValue());
                    } else if(entry.getValue() instanceof Double){
                        validateMap.put("check",entry.getKey());
                        validateMap.put("comparator","num_eq");
                        validateMap.put("expect",((Double)entry.getValue()).intValue());
                        //validate.setExpect(((Double)entry.getValue()).intValue()+"");
                    } else if(entry.getValue() instanceof Map){
                        validateMap.put("check",entry.getKey()+".size()");
                        validateMap.put("comparator","num_eq");
                        validateMap.put("expect",((Map)entry.getValue()).size());
                    } else if(entry.getValue() instanceof List){
                        validateMap.put("check",entry.getKey()+".size()");
                        validateMap.put("comparator","num_eq");
                        validateMap.put("expect",((List)entry.getValue()).size());
                    } else if(entry.getValue() instanceof Boolean){
                        validateMap.put("check",entry.getKey());
                        validateMap.put("comparator","is");
                        validateMap.put("expect",(entry.getValue()));
                    }
                    if(validateMap.size()>0) {
                        validateList.add(validateMap);
                    }
                }
                List<HarCookie> harCookies = harRequest.getCookies();
                for(HarCookie harCookie : harCookies){
                    request.getCookies().put(harCookie.getName(),harCookie.getValue());
                }
                testMap.put("test",testCase);
                testCases.add(testMap);
            }
        }
        System.out.println("开始转换Yaml文件："+ymlFileName);
        YamlRead yamlRead = new YamlRead();
        yamlRead.writeYaml(testCases,ymlFileName);
        System.out.println("转换结束");
    }

    private static void printArgsTips(){
        System.out.println("请输以下参数");
        System.out.println("arg0: har文件路径 必填");
        System.out.println("arg1: yml文件名 必填");
        System.out.println("arg2: 包含的字符 多个以斜杆‘/’分隔，只有URL包含该字符才会转化 可选");
        System.out.println("arg3: 不包含的字符 多个以斜杆‘/’分隔 只有URL不包含该字符才会转化 可选");
    }

    private static boolean containstr(String str,String[] s){
        if(str==null || s==null){
            return false;
        }
        boolean flag=false;
        for (int i = 0; i < s.length; i++) {
            if (str.contains(s[i])) {
                flag = true;
            }else {
                flag = false;
            }
        }
        return flag;
    }
}
